<!doctype html>
<html lang="zh-CN">
<head>
  <meta charset="utf-8" />
  <meta name="viewport" content="width=device-width, initial-scale=1" />
  <title>医生端控制台（乳腺癌术后）</title>
  <style>
    :root { --bg:#f7f9fc; --text:#111827; --card:#fff; --border:#e5e7eb; --primary:#2563eb; --muted:#6b7280; --header-bg:#1f2937; --header-text:#fff; --row-alt:#f9fafb; }
    .dark { --bg:#0f172a; --text:#e5e7eb; --card:#111827; --border:#334155; --primary:#4f46e5; --muted:#94a3b8; --header-bg:#0b1220; --header-text:#e5e7eb; --row-alt:#0b162c; }
    body { font-family: -apple-system,'Segoe UI',Roboto,'PingFang SC','Microsoft YaHei',sans-serif; margin:0; padding:0; background:var(--bg); color:var(--text); }
    header { background:var(--header-bg); color:var(--header-text); padding:16px 20px; display:flex; align-items:center; justify-content:space-between; }
    header nav { display:flex; gap:8px; align-items:center; }
    main { padding:16px; max-width:1080px; margin:0 auto; }
    .grid { display:grid; grid-template-columns: 1fr 1fr; gap:16px; }
    .card { background:var(--card); border:1px solid var(--border); border-radius:12px; padding:16px; box-shadow:0 1px 2px rgba(0,0,0,0.06); transition: transform .12s ease, box-shadow .12s ease; }
    .card:hover { transform: translateY(-1px); box-shadow: 0 8px 16px rgba(0,0,0,0.10); }
    table { width:100%; border-collapse:collapse; font-size:13px; }
    thead th { background: var(--row-alt); font-weight:600; }
    th, td { border-bottom:1px solid var(--border); padding:6px 8px; text-align:left; }
    tbody tr:nth-child(odd) { background: var(--row-alt); }
    tbody tr:hover { background: rgba(99,102,241,0.06); }
    .actions { display:flex; gap:8px; }
    button { padding:8px 12px; border:0; border-radius:8px; background:var(--primary); color:var(--header-text); cursor:pointer; transition: filter .12s ease, opacity .12s ease; }
    button:hover { filter: brightness(1.05); }
    button:disabled { opacity:.6; cursor:not-allowed; }
    .secondary { background:var(--muted); color:var(--header-text); }
    .ghost { background: transparent; color: var(--header-text); border: 1px solid rgba(255,255,255,0.25); }
    a.ghost { background: transparent; color: var(--header-text); border: 1px solid rgba(255,255,255,0.25); padding:8px 12px; border-radius:8px; text-decoration:none; }
    a.ghost:hover { border-color: rgba(255,255,255,0.5); }
    pre { white-space:pre-wrap; word-wrap:break-word; }
    .toast { position:fixed; right:20px; bottom:20px; background: var(--text); color: var(--card); padding:10px 14px; border-radius:10px; opacity:0; transform:translateY(10px); transition:all .2s; }
    .toast.show { opacity:1; transform:translateY(0); }
  </style>
</head>
<body>
  <header>
    <h2>医生端控制台 — 乳腺癌术后</h2>
    <nav><a class="ghost" href="/">主页</a><a class="ghost" href="/patient">用户端</a></nav>
    <div class="actions"><button id="toggle-theme" class="ghost">切换主题</button></div>
  </header>
  <main>
    <div class="grid">
      <div class="card">
        <h3>关键统计</h3>
        <div id="stats">加载中...</div>
        <div class="actions" style="margin-top:10px">
          <button id="seed" class="secondary">导入示例数据</button>
          <button id="refresh">刷新</button>
        </div>
        <p style="color:var(--muted);font-size:13px;margin-top:8px">适用场景：乳腺癌术后上肢康复；关注指标：功能评分、异常概率与训练反馈。</p>
      </div>
      <div class="card">
        <h3>最新计划</h3>
        <div id="plan-view">加载中...</div>
      </div>
    </div>

    <div class="grid" style="margin-top:12px">
      <div class="card">
        <h3>评估记录</h3>
        <table>
          <thead><tr><th>时间</th><th>评分</th><th>异常概率(%)</th></tr></thead>
          <tbody id="eval-tbody"></tbody>
        </table>
      </div>
      <div class="card">
        <h3>训练反馈</h3>
        <table>
          <thead><tr><th>时间</th><th>依从度(%)</th><th>疼痛(0-10)</th><th>时长(分钟)</th><th>备注</th></tr></thead>
          <tbody id="fb-tbody"></tbody>
        </table>
      </div>
    </div>
    <div id="toast" class="toast"></div>
  </main>
  <script>
    async function fetchStats(){
      try{
        const r = await fetch('/api/stats');
        const s = await r.json();
        document.getElementById('stats').textContent = `评估次数：${s.count}，平均评分：${(s.avg_score??0).toFixed(2)}，平均异常概率：${Math.round((s.avg_anomaly_prob??0)*100)}%`;
      }catch(e){ document.getElementById('stats').textContent = '统计加载失败'; }
    }
    async function fetchPlan(){
      try{
        const r = await fetch('/api/plan');
        if(r.ok){ const d = await r.json(); renderPlanView(d.plan); }
        else { document.getElementById('plan-view').innerHTML = '<em>暂无计划</em>'; }
      }catch(e){ document.getElementById('plan-view').innerHTML = '<em>计划加载失败</em>'; }
    }
    async function fetchEvaluations(){
      try{
        const r = await fetch('/api/evaluations');
        const d = await r.json();
        const items = d.items || [];
        const tbody = document.getElementById('eval-tbody');
        tbody.innerHTML = '';
        items.slice(-20).forEach(i => {
          const tr = document.createElement('tr');
          tr.innerHTML = `<td>${i.timestamp}</td><td>${i.score}</td><td>${Math.round(i.anomaly_prob*100)}</td>`;
          tbody.appendChild(tr);
        });
      }catch(e){
        const tbody = document.getElementById('eval-tbody');
        tbody.innerHTML = '<tr><td colspan="3">评估记录加载失败</td></tr>';
      }
    }
    async function fetchFeedbacks(){
      try{
        const r = await fetch('/api/feedbacks');
        const d = await r.json();
        const items = d.items || [];
        const tbody = document.getElementById('fb-tbody');
        tbody.innerHTML = '';
        items.slice(-20).forEach(i => {
          const tr = document.createElement('tr');
          tr.innerHTML = `<td>${i.timestamp}</td><td>${i.adherence}</td><td>${i.pain}</td><td>${i.duration_minutes}</td><td>${i.note}</td>`;
          tbody.appendChild(tr);
        });
      }catch(e){
        const tbody = document.getElementById('fb-tbody');
        tbody.innerHTML = '<tr><td colspan="5">训练反馈加载失败</td></tr>';
      }
    }
    async function seed(){
      const btn = document.getElementById('seed');
      btn.disabled = true; const old = btn.textContent; btn.textContent = '导入中...';
      try{
        const r = await fetch('/api/mock/seed', { method:'POST' });
        if(r.ok){ showToast('示例数据已导入'); await refreshAll(); }
        else { showToast('导入失败'); }
      }catch(e){ showToast('导入失败'); }
      finally { btn.disabled = false; btn.textContent = old; }
    }
    async function refreshAll(){ await fetchStats(); await fetchPlan(); await fetchEvaluations(); await fetchFeedbacks(); }
    document.getElementById('seed').addEventListener('click', seed);
    document.getElementById('refresh').addEventListener('click', refreshAll);
    refreshAll();
    // 主题切换
    const savedTheme = localStorage.getItem('theme');
    if(savedTheme === 'dark'){ document.documentElement.classList.add('dark'); }
    document.getElementById('toggle-theme').addEventListener('click', () => {
      const isDark = document.documentElement.classList.toggle('dark');
      localStorage.setItem('theme', isDark ? 'dark' : 'light');
    });
    function showToast(msg){ const el=document.getElementById('toast'); el.textContent=msg; el.classList.add('show'); setTimeout(()=>el.classList.remove('show'),1500); }
    function renderPlanView(plan){
      const el = document.getElementById('plan-view');
      if(!plan){ el.innerHTML = '<em>暂无计划</em>'; return; }
      const levelMap = { beginner: '初级', intermediate: '中级', advanced: '高级' };
      const level = levelMap[plan.level] || plan.level || '中级';
      const reps = plan.reps ?? 10;
      const sets = plan.sets ?? 3;
      const rest = plan.rest_seconds ?? 60;
      const exercises = (plan.exercises || []).map(x => {
        const name = x.name || '动作';
        const dur = x.duration_min ?? 5;
        const cue = x.cue || '';
        return `<li>${name} — ${dur}分钟${cue ? '（提示：'+cue+'）' : ''}</li>`;
      }).join('');
      el.innerHTML = `
        <div>等级：${level}；次数：${reps}；组数：${sets}；休息：${rest}秒</div>
        <div style="margin-top:6px">动作列表：</div>
        <ul style="margin:6px 0 0 18px">${exercises || '<li>无</li>'}</ul>
      `;
    }
  </script>
</body>
</html>